package com.cnap.multiclouldmgmt.service.impl;

import com.alibaba.fastjson.JSONObject;
import com.cnap.multiclouldmgmt.MulticlouldmgmtApplicationTests;
import com.cnap.multiclouldmgmt.model.dockerHarborModel.DestRegistryModel;
import com.cnap.multiclouldmgmt.model.dockerHarborModel.PolicyModel;
import com.cnap.multiclouldmgmt.model.dockerHarborModel.ProjectInfoModel;
import com.cnap.multiclouldmgmt.model.k8sModels.K8sClusterBasicModel;
import com.cnap.multiclouldmgmt.model.vm.VmModel;
import com.cnap.multiclouldmgmt.service.DockerHarborService;
import com.cnap.multiclouldmgmt.service.MultiCloudMgmtService;
import com.cnap.multiclouldmgmt.util.CnapCloudMgmtConstants;
import org.apache.http.Header;
import org.apache.http.HttpEntity;
import org.apache.http.StatusLine;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.impl.client.CloseableHttpClient;
import org.junit.jupiter.api.Test;
import org.mockito.Mock;
import org.mockito.Mockito;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.mock.mockito.MockBean;

import java.io.*;
import java.util.ArrayList;
import java.util.List;

import static org.mockito.ArgumentMatchers.any;

class DockerHarborServiceImplTest extends MulticlouldmgmtApplicationTests {

    @Autowired
    private DockerHarborService dockerHarborService;

    @Mock
    private CloseableHttpClient httpClient;

    @Test
    void getHarboPlolicy() {

    }

    @Test
    void delProjectImages() {
    }

    @Test
    void delProject() {
    }

    @Test
    void registerRemoteHarbor() throws IOException {

        httpClient = Mockito.mock(CloseableHttpClient.class);
        CloseableHttpResponse response = Mockito.mock(CloseableHttpResponse.class);
        Mockito.when(httpClient.execute(any(HttpPost.class))).thenReturn(response);
        StatusLine statusLine = Mockito.mock(StatusLine.class);
        Mockito.when(response.getStatusLine()).thenReturn(statusLine);
        Mockito.when(statusLine.getStatusCode()).thenReturn(200);
        DockerHarborServiceImpl.setHttpClient(httpClient);
        dockerHarborService.registerRemoteHarbor(CnapCloudMgmtConstants.TEST_ADMIN);


    }

    @Test
    void getAllRegisterHarbor() throws IOException {

        httpClient = Mockito.mock(CloseableHttpClient.class);
        CloseableHttpResponse response = Mockito.mock(CloseableHttpResponse.class);
        Mockito.when(httpClient.execute(any(HttpGet.class))).thenReturn(response);
        StatusLine statusLine = Mockito.mock(StatusLine.class);
        Mockito.when(response.getStatusLine()).thenReturn(statusLine);
        Mockito.when(statusLine.getStatusCode()).thenReturn(200);
        List<DestRegistryModel> result = new ArrayList<>();
        DestRegistryModel destRegistryModel = new DestRegistryModel();
        destRegistryModel.setName("name");
        result.add(destRegistryModel);

        HttpEntity httpEntity = new HttpEntity() {
            @Override
            public boolean isRepeatable() {
                return false;
            }

            @Override
            public boolean isChunked() {
                return false;
            }

            @Override
            public long getContentLength() {
                return 0;
            }

            @Override
            public Header getContentType() {
                return null;
            }

            @Override
            public Header getContentEncoding() {
                return null;
            }

            @Override
            public InputStream getContent() throws IOException, UnsupportedOperationException {
                String content = JSONObject.toJSONString(result);
                return new ByteArrayInputStream(new String(content).getBytes());
            }

            @Override
            public void writeTo(OutputStream outputStream) throws IOException {

            }

            @Override
            public boolean isStreaming() {
                return false;
            }

            @Override
            public void consumeContent() throws IOException {

            }
        };
        Mockito.when(response.getEntity()).thenReturn(httpEntity);
        DockerHarborServiceImpl.setHttpClient(httpClient);
        List<DestRegistryModel> destRegistryModels = dockerHarborService.getAllRegisterHarbor(CnapCloudMgmtConstants.TEST_ADMIN);
    }

    @Test
    void addPolicy() throws IOException {

        httpClient = Mockito.mock(CloseableHttpClient.class);
        CloseableHttpResponse response = Mockito.mock(CloseableHttpResponse.class);
        Mockito.when(httpClient.execute(any(HttpPost.class))).thenReturn(response);
        StatusLine statusLine = Mockito.mock(StatusLine.class);
        Mockito.when(response.getStatusLine()).thenReturn(statusLine);
        Mockito.when(statusLine.getStatusCode()).thenReturn(200);
        DockerHarborServiceImpl.setHttpClient(httpClient);

        DestRegistryModel destRegistryModel = new DestRegistryModel();
        dockerHarborService.addPolicy(CnapCloudMgmtConstants.TEST_ADMIN,destRegistryModel,"pro");
    }

    @Test
    void addHarborProject() throws IOException {

        httpClient = Mockito.mock(CloseableHttpClient.class);
        CloseableHttpResponse response = Mockito.mock(CloseableHttpResponse.class);
        Mockito.when(httpClient.execute(any(HttpPost.class))).thenReturn(response);
        StatusLine statusLine = Mockito.mock(StatusLine.class);
        Mockito.when(response.getStatusLine()).thenReturn(statusLine);
        Mockito.when(statusLine.getStatusCode()).thenReturn(200);
        DockerHarborServiceImpl.setHttpClient(httpClient);

        DestRegistryModel destRegistryModel = new DestRegistryModel();
        dockerHarborService.addHarborProject(CnapCloudMgmtConstants.TEST_ADMIN,"pro");
    }

    @Test
    void getAllHarborProject() throws IOException {

        httpClient = Mockito.mock(CloseableHttpClient.class);
        CloseableHttpResponse response = Mockito.mock(CloseableHttpResponse.class);
        Mockito.when(httpClient.execute(any(HttpGet.class))).thenReturn(response);
        StatusLine statusLine = Mockito.mock(StatusLine.class);
        Mockito.when(response.getStatusLine()).thenReturn(statusLine);
        Mockito.when(statusLine.getStatusCode()).thenReturn(200);
        List<ProjectInfoModel> result = new ArrayList<>();
        ProjectInfoModel projectInfoModel = new ProjectInfoModel();
        projectInfoModel.setName("name");
        result.add(projectInfoModel);

        HttpEntity httpEntity = new HttpEntity() {
            @Override
            public boolean isRepeatable() {
                return false;
            }

            @Override
            public boolean isChunked() {
                return false;
            }

            @Override
            public long getContentLength() {
                return 0;
            }

            @Override
            public Header getContentType() {
                return null;
            }

            @Override
            public Header getContentEncoding() {
                return null;
            }

            @Override
            public InputStream getContent() throws IOException, UnsupportedOperationException {
                String content = JSONObject.toJSONString(result);
                return new ByteArrayInputStream(new String(content).getBytes());
            }

            @Override
            public void writeTo(OutputStream outputStream) throws IOException {

            }

            @Override
            public boolean isStreaming() {
                return false;
            }

            @Override
            public void consumeContent() throws IOException {

            }
        };
        Mockito.when(response.getEntity()).thenReturn(httpEntity);
        DockerHarborServiceImpl.setHttpClient(httpClient);
        dockerHarborService.getAllHarborProject(CnapCloudMgmtConstants.TEST_ADMIN);
    }

    @Test
    void createClusterHarborCopyRule() throws IOException {
        dockerHarborService.createClusterHarborCopyRule(CnapCloudMgmtConstants.TEST_ADMIN,
                CnapCloudMgmtConstants.TEST_ADMIN);
        dockerHarborService.createClusterHarborCopyRule(CnapCloudMgmtConstants.CNAP_VM_MASTER,
                CnapCloudMgmtConstants.CNAP_VM_MASTER);
    }

    @Test
    void getAllPolicies() throws IOException {

        httpClient = Mockito.mock(CloseableHttpClient.class);
        CloseableHttpResponse response = Mockito.mock(CloseableHttpResponse.class);
        Mockito.when(httpClient.execute(any(HttpGet.class))).thenReturn(response);
        StatusLine statusLine = Mockito.mock(StatusLine.class);
        Mockito.when(response.getStatusLine()).thenReturn(statusLine);
        Mockito.when(statusLine.getStatusCode()).thenReturn(200);
        List<PolicyModel> result = new ArrayList<>();
        PolicyModel projectInfoModel = new PolicyModel();
        projectInfoModel.setName("name");
        result.add(projectInfoModel);

        HttpEntity httpEntity = new HttpEntity() {
            @Override
            public boolean isRepeatable() {
                return false;
            }

            @Override
            public boolean isChunked() {
                return false;
            }

            @Override
            public long getContentLength() {
                return 0;
            }

            @Override
            public Header getContentType() {
                return null;
            }

            @Override
            public Header getContentEncoding() {
                return null;
            }

            @Override
            public InputStream getContent() throws IOException, UnsupportedOperationException {
                String content = JSONObject.toJSONString(result);
                return new ByteArrayInputStream(new String(content).getBytes());
            }

            @Override
            public void writeTo(OutputStream outputStream) throws IOException {

            }

            @Override
            public boolean isStreaming() {
                return false;
            }

            @Override
            public void consumeContent() throws IOException {

            }
        };
        Mockito.when(response.getEntity()).thenReturn(httpEntity);
        DockerHarborServiceImpl.setHttpClient(httpClient);
        dockerHarborService.getAllPolicies(null,CnapCloudMgmtConstants.TEST_ADMIN);
    }

    @Test
    void syncExistImages() {
    }

    @MockBean
    private MultiCloudMgmtService multiCloudMgmtService;

    @Test
    void delPolicy() throws Exception {

        K8sClusterBasicModel k8sClusterBasicModel = new K8sClusterBasicModel();
        k8sClusterBasicModel.setK8sClusterIp("1.1.1.1");
        k8sClusterBasicModel.setK8sClusterName(CnapCloudMgmtConstants.TEST_ADMIN);
        k8sClusterBasicModel.setVmModels(new ArrayList<>());

        VmModel masterModel = new VmModel();
        masterModel.setK8sCluterRole(CnapCloudMgmtConstants.CNAP_VM_MASTER);
        k8sClusterBasicModel.getVmModels().add(masterModel);
        VmModel workModel = new VmModel();
        workModel.setK8sCluterRole(CnapCloudMgmtConstants.CNAP_VM_WORKER);
        k8sClusterBasicModel.getVmModels().add(workModel);

        Mockito.when(multiCloudMgmtService.getK8sClientByIp("1.1.1.1"))
                .thenReturn(k8sClusterBasicModel);
        dockerHarborService.delProjectImages("1.1.1.1");

    }

    @Test
    void doImageCopy() throws IOException {

        httpClient = Mockito.mock(CloseableHttpClient.class);
        CloseableHttpResponse response = Mockito.mock(CloseableHttpResponse.class);
        Mockito.when(httpClient.execute(any(HttpPost.class))).thenReturn(response);
        StatusLine statusLine = Mockito.mock(StatusLine.class);
        Mockito.when(response.getStatusLine()).thenReturn(statusLine);
        Mockito.when(statusLine.getStatusCode()).thenReturn(200);
        DockerHarborServiceImpl.setHttpClient(httpClient);

        DestRegistryModel destRegistryModel = new DestRegistryModel();
        dockerHarborService.doImageCopy(CnapCloudMgmtConstants.TEST_ADMIN,"16");
    }
}